﻿using System;
using System.Collections.Generic;
using System.Text;
using Microsoft.Practices.EnterpriseLibrary.Validation;
using Microsoft.Practices.EnterpriseLibrary.Validation.Validators; 

namespace Sinacor.Infra.Service.Validation
{
    /// <summary>
    /// Classe base para implementação de atributos de validação
    /// Todas as classes da infra que representam atributos de validação
    /// deverão herdar desta classe
    /// Esta classe herda de classe base da Enterprise Library que define atributos de validação
    /// </summary>
    [AttributeUsage(AttributeTargets.Property, AllowMultiple=true)]
    public abstract class SinacorBaseValidatorAttribute : Attribute //: ValidatorAttribute
    {
        private int _codException;
        internal int CodException
        {
            get { return _codException; }
        }

        private string _messageTemplate;
        public string MessageTemplate
        {
            get { return _messageTemplate; }
            set { _messageTemplate = value; }
        }

        private string _ruleset;
        public string Ruleset
        {
            get { return _ruleset; }
            set { _ruleset = value; }
        }

        private bool _ignoreNulls;
        public bool IgnoreNulls
        {
            get { return _ignoreNulls; }
            set { _ignoreNulls = value; }
        }

        /// <summary>
        /// Construtor da classe
        /// </summary>
        /// <param name="codException">Código de exceção a ser gerada caso a validação retorne falha</param>
        public SinacorBaseValidatorAttribute(int codException)
        {
            this._codException = codException;
            this._ruleset = "";
            this._ignoreNulls = false;
        }

        /// <summary>
        /// Construtor da classe (sobrecarga)
        /// </summary>
        /// <param name="codException">Código de exceção a ser gerada caso a validação retorne falha</param>
        /// <param name="ignoreNulls">Se a validacao deve retornar sucesso em caso de valores nulos</param>
        public SinacorBaseValidatorAttribute(int codException, bool ignoreNulls) 
            : this(codException)
        {
            this._ignoreNulls = ignoreNulls;
        }

        /// <summary>
        /// Construtor da classe (sobrecarga)
        /// </summary>
        /// <param name="codException">Código de exceção a ser gerada caso a validação retorne falha</param>
        /// <param name="ruleset">Usado em casos onde a validação na entidade só deve ocorrer em 
        /// determinadas situações</param>
        public SinacorBaseValidatorAttribute(int codException, string ruleset) 
            : this(codException)
        {
            this._ruleset = ruleset;
        }

        /// <summary>
        /// Construtor da classe (sobrecarga)
        /// </summary>
        /// <param name="codException">Código de exceção a ser gerada caso a validação retorne falha</param>
        /// <param name="ruleset">Usado em casos onde a validação na entidade só deve ocorrer em 
        /// determinadas situações</param>
        /// <param name="ignoreNulls">Se a validacao deve retornar sucesso em caso de valores nulos</param>
        public SinacorBaseValidatorAttribute(int codException, string ruleset, bool ignoreNulls) 
            : this(codException, ruleset)
        {
            this._ignoreNulls = ignoreNulls;
        }


        /// <summary>
        /// Método abstrato para criação do objeto de validação, que é quem contém a regra de validação
        /// propriamente dita
        /// </summary>
        /// <returns>
        /// Objeto do tipo Validator (tipo definido na Enterprise Library).
        /// A classe que implementar este método deve retornar um objeto especializado, que
        /// herda de Validator.
        /// </returns>
        //protected abstract Validator CreateValidator();
        public abstract Validator CreateValidator();

        /// <summary>
        /// Método responsável por retornar o objeto de validação a ser utilizado na validação.
        /// É implementação requerida pela classe base, onde este método é abstract.
        /// </summary>
        /// <param name="targetType"></param>
        /// <returns>Objeto do tipo Validator (tipo definido na Enterprise Library)</returns>
        //protected override Validator DoCreateValidator(Type targetType)
        //{
        //    return CreateValidator();
        //}

    }
}
